#include "s3e.h"
#include "Iw2D.h"
#include <list>
#include "block.h"
#include "IwRandom.h"
#include "util.h"
#include "game.h"
#include "engine.h"
#include "grid.h"

#include <assert.h>


int BlockSize = 0;

Grid::Grid()	:
	m_NextBlockIndex(Rand()%(Block::MAX + 1)),
	m_NextBlockType( (Block::T_TYPE)(Rand()%(((int)Block::MAX)) + 1) ),
	m_NextBlockRotation(Rand()%4),
	m_CurrentGroupID(0),
	m_BlockWasMoved(false),
	m_BlockMoveTimer(0.0f),
	m_BlockTypeImages(NULL),
	m_DefaultBlockImage(NULL),
	m_Background(NULL)
{
	for (int i = 0; i < 4; ++i)
	{
		m_CurBlocks[i] = NULL;
	}

	m_CurBlockPattern = Rand()%(Block::MAX + 1);
	m_CurBlockRotation = Rand()%4;

	m_Blocks = new Block*[200];	// Dimensions are 10 by 20.

	for (int i = 0; i < 200; ++i)
	{
		m_Blocks[i] = new Block(i);
	}

	m_BlockTypeImages = new CIw2DImage*[Block::MAX];

	BlockSize = (int)min( TO_SCREENX(37.0f), TO_SCREENY(37.0f) );
	m_BlockSize = (float)BlockSize;
	
	const float GridBGScaleX = (( 10 * BlockSize + 11 ) / 381.0f);
	const float GridBGScaleY = (( 20 * BlockSize + 21 ) / 761.0f);
	CIwSVec2 GridBGSize = CIwSVec2( int16(393.0f * GridBGScaleX), 
									int16(773.0f * GridBGScaleY) );

	m_Background = Iw2DCreateImageResource("grid_bg");
	m_GridBGSize = GridBGSize;
	m_GridTopLeft = CIwSVec2(	int16( TO_SCREENX(28.0f) ), 
								int16( Iw2DGetSurfaceHeight() - TO_SCREENY(27.0f) - (20 * BlockSize + 21) ) );
	m_GridBGTopLeft = CIwSVec2( int16(m_GridTopLeft.x - (5.0f * GridBGScaleX)), int16(m_GridTopLeft.y - (6.0f * GridBGScaleY)) );


	m_DefaultBlockImage = Iw2DCreateImageResource("block_default");

	// To make sure each block type has an image associated with it..
	for (int i = 0; i < Block::MAX; ++i)
	{
		m_BlockTypeImages[i] = m_DefaultBlockImage;
	}

	m_BlockTypeImages[Block::NONE]		= Iw2DCreateImageResource("block_none");
	m_BlockTypeImages[Block::WHITE]		= Iw2DCreateImageResource("block_white");
	m_BlockTypeImages[Block::BLUE]		= Iw2DCreateImageResource("block_blue");
	m_BlockTypeImages[Block::GREEN]		= Iw2DCreateImageResource("block_green");
	m_BlockTypeImages[Block::RED]		= Iw2DCreateImageResource("block_red");
	m_BlockTypeImages[Block::ORANGE]	= Iw2DCreateImageResource("block_orange");
	m_BlockTypeImages[Block::YELLOW]	= Iw2DCreateImageResource("block_yellow");
	m_BlockTypeImages[Block::PURPLE]	= Iw2DCreateImageResource("block_purple");
	m_BlockTypeImages[Block::MAX]		= Iw2DCreateImageResource("block_white");

	// Build the structures in the structure array.
	int blockPatterns[8][4][4][4] = 
	{
		{								// |--------|
			{	{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 0, 1, 0 },			// |    //  |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 1, 1, 0, 0 },			// |////    |
				{ 0, 0, 0, 0 },		},  // |        |
										// |--------|
			{	{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 0, 1, 0 },			// |    //  |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 1, 1, 0, 0 },			// |////    |
				{ 0, 0, 0, 0 },		},  // |        |
		},								// |--------|
		{								// |--------|
			{	{ 0, 0, 1, 0 },			// |    //  |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 1, 1, 0, 0 },			// |////    |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 0, 0, 0 },		},  // |        |
										// |--------|
			{	{ 0, 0, 1, 0 },			// |    //  |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 1, 1, 0, 0 },			// |////    |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 0, 0, 0 },		},  // |        |
		},								// |--------|
		{								// |--------|
			{	{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 1, 1, 1, 0 },			// |//////  |
				{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 0, 0, 0 },		},  // |        |
										// |--------|
			{	{ 0, 1, 0, 0 },			// |  //    |
				{ 1, 1, 0, 0 },			// |////    |
				{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 1, 0, 0 },			// |  //    |
				{ 1, 1, 1, 0 },			// |//////  |
				{ 0, 0, 0, 0 },			// |        |
				{ 0, 0, 0, 0 },		},  // |        |
		},								// |--------|
		{								// |--------|
			{	{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 1, 1, 1, 0 },			// |//////  |
				{ 1, 0, 0, 0 },			// |//      |
				{ 0, 0, 0, 0 },		},  // |        |
										// |--------|
			{	{ 1, 1, 0, 0 },			// |////    |
				{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 0, 1, 0 },			// |    //  |
				{ 1, 1, 1, 0 },			// |//////  |
				{ 0, 0, 0, 0 },			// |        |
				{ 0, 0, 0, 0 },		},  // |        |
		},								// |--------|
		{								// |--------|
			{	{ 0, 0, 1, 0 },			// |    //  |
				{ 0, 0, 1, 0 },			// |    //  |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 1, 1 },			// |  //////|
				{ 0, 0, 0, 0 },			// |        |
				{ 0, 0, 0, 0 },		},  // |        |
										// |--------|
			{	{ 0, 0, 1, 1 },			// |    ////|
				{ 0, 0, 1, 0 },			// |    //  |
				{ 0, 0, 1, 0 },			// |    //  |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 0, 1, 1, 1 },			// |  //////|
				{ 0, 0, 0, 1 },			// |      //|
				{ 0, 0, 0, 0 },		},  // |        |
		},								// |--------|
		{								// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 1, 1, 0 },			// |  ////  |
				{ 0, 0, 0, 0 },		},	// |        |
		},								// |--------|
		{								// |--------|
			{	{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 0, 0 },		},	// |  //    |
										// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 1, 1, 1, 1 },			// |////////|
				{ 0, 0, 0, 0 },			// |        |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
			{	{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 0, 0 },			// |  //    |
				{ 0, 1, 0, 0 },		},	// |  //    |
										// |--------|
			{	{ 0, 0, 0, 0 },			// |        |
				{ 1, 1, 1, 1 },			// |////////|
				{ 0, 0, 0, 0 },			// |        |
				{ 0, 0, 0, 0 },		},	// |        |
										// |--------|
		},
		{
			{	{0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0},  },
			{	{0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0},  },
			{	{0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0},  },
			{	{0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0},  },
		}
	}; // Block blockPatterns[8][4][4][4]
	for (int t = 0; t < 8; ++t)
		for (int r = 0; r < 4; ++r)
			for (int x = 0; x < 4; ++x)
				for (int y = 0; y < 4; ++y)
					m_BlockPatterns[t][r][x][y] = (blockPatterns[t][r][y][x] == 1);
}

Grid::~Grid()
{
	if(m_Blocks)
	{
		for(int i = 0; i < 200; ++i)
			delete m_Blocks[i];
		delete[] m_Blocks;
	}
	m_Blocks = NULL;

	if (m_BlockTypeImages)
	{
		for (int i = Block::MAX; i >= 0; --i)
		{
			delete m_BlockTypeImages[i];
			m_BlockTypeImages[i] = NULL;
		}
		delete[] m_BlockTypeImages;
	}
	m_BlockTypeImages = NULL;

	if (m_DefaultBlockImage)
		delete m_DefaultBlockImage;
	m_DefaultBlockImage = NULL;

	if (m_Background)
		delete m_Background;
	m_Background = NULL;

	if (m_Blocks)
	{
		for (int i = 0; i < 200; ++i)
		{
			delete m_Blocks[i];
			m_Blocks[i] = NULL;
		}
		delete[] m_Blocks;
	}
	m_Blocks = NULL;
}

void Grid::ClearLine( int a_Line )
{
	float lineStart = float(a_Line * 10);
	for(int i = (int)lineStart; i < lineStart + 10; ++i)
	{
		// Do any special events for the blocks.
		switch(m_Blocks[i]->GetType())
		{
		case Block::MAX:
			{
				break;
			}
		//default:
		//	{
		//		// Do nothing...
		//	}
		}
	}

	for(int i = (int)lineStart; i < lineStart + 10; ++i)
	{
		m_Blocks[i]->SetType( Block::NONE );
		m_Blocks[i]->SetGroupID( 0 );
		m_Blocks[i]->SetStatic( false );
		m_Blocks[i]->SetHasMoved( false );
	}

	for(int i = a_Line - 1; i >= 0; --i)
	{
		lineStart = float(i * 10);
		for(int j = 0; j < 10; ++j)
		{
			SwapBlocks(int(lineStart + j), int(lineStart + j + 10));
		}
	}
}

void Grid::CheckLines()
{
	for (int line = 0; line < 20; ++line)
	{
		const int lineStart = line * 10;
		if( m_Blocks[lineStart    ]->GetType() != Block::NONE &&
			m_Blocks[lineStart + 1]->GetType() != Block::NONE &&
			m_Blocks[lineStart + 2]->GetType() != Block::NONE &&
			m_Blocks[lineStart + 3]->GetType() != Block::NONE &&
			m_Blocks[lineStart + 4]->GetType() != Block::NONE &&
			m_Blocks[lineStart + 5]->GetType() != Block::NONE &&
			m_Blocks[lineStart + 6]->GetType() != Block::NONE &&
			m_Blocks[lineStart + 7]->GetType() != Block::NONE &&
			m_Blocks[lineStart + 8]->GetType() != Block::NONE &&
			m_Blocks[lineStart + 9]->GetType() != Block::NONE)
		{
			ClearLine(line);
			Game::GetSingletonPtr()->IncrementScore(10);

			// Increase the game speed. (Actually, decrease the time between each 'move' of blocks).
			static int NumRowsToCompleteBeforeMaxGameSpeed = 75;	// This is stored in a variable here just to make it clearer
																	// how to edit it.
			Game::GetSingletonPtr()->m_BlockMoveInterval -= (GAME_MOVE_INTERVAL_MAX - GAME_MOVE_INTERVAL_MIN) * (1.0f/NumRowsToCompleteBeforeMaxGameSpeed);
			if (Game::GetSingletonPtr()->m_BlockMoveInterval < GAME_MOVE_INTERVAL_MIN)
			{
				Game::GetSingletonPtr()->m_BlockMoveInterval = GAME_MOVE_INTERVAL_MIN;
			}
		}
	}
}
void Grid::Update( float a_DT )
{
	m_BlockMoveTimer += a_DT;

	if (m_BlockMoveTimer >= Game::GetSingletonPtr()->m_BlockMoveInterval)
	{
		m_BlockMoveTimer = 0.0f;
		m_BlockWasMoved = false;

		// Reset the 'has-moved' state of all blocks for this frame.
		for (int i = 0; i < 200; ++i)
		{
			m_Blocks[i]->SetHasMoved(false);
		}

		if (m_CurBlocks[0] != NULL && 
			m_CurBlocks[1] != NULL && 
			m_CurBlocks[2] != NULL && 
			m_CurBlocks[3] != NULL)	// m_CurBlocks can be NULL before the first blocks are spawned, these are not spawned immediately
									// because that will cause issues.
		{
			for(int i = 3; i >= 0; --i)
			{
				const int index = m_CurBlocks[i]->GetIndex();
				if (   index < 190 && !m_CurBlocks[i]->IsStatic() && 
					(m_Blocks[index + 10]->GetType() == Block::NONE || m_CurrentGroupID == m_Blocks[index + 10]->GetGroupID()))
				{
					m_CurBlocks[i]->SetHasMoved(true);

					SwapBlocks(index, index + 10);

					// Indicate that a block was moved.
					m_BlockWasMoved = true;
					if(i == 0)
						m_CurBlockPos.y++;
				}
				else
				{
					for(int j = 0; j < 4; ++j)
					{
						// Indicate it is static.
						m_CurBlocks[j]->SetStatic(true);

						// If the block has been moved already this frame...
						if (m_CurBlocks[j]->HasMoved())
						{
							// Move it back.
							m_CurBlocks[j]->SetHasMoved(false);

							SwapBlocks(m_CurBlocks[j]->GetIndex(), m_CurBlocks[j]->GetIndex() - 10);
						}
					}
				}
			}
		}
	}
	else
	{
		// If m_BlockWasMoved is false, no block has been moved since the last time the grid was checked.
		// This means that a new set of blocks can be spawned.
		if (!m_BlockWasMoved)
		{
			m_BlockWasMoved = true;

			// Spawn new blocks.
			SpawnBlocks(m_NextBlockIndex, m_NextBlockRotation);

			// Check the grid to see if any lines have been completed.
			CheckLines();

			// Pick a new block index to spawn next.
			m_NextBlockIndex = Rand()%7;
			// Pick a new block type to spawn next.
			m_NextBlockType = (Block::T_TYPE)(Rand()%(((int)Block::MAX)) + 1);
			// Pick a new block rotation to use at the next spawn.
			m_NextBlockRotation = Rand()%4;

			m_BlockMoveTimer = 0.0f;
		}
	}
}

void Grid::Render( float a_DT )
{
	CIwSVec2 BlockSize = CIwSVec2( int16(m_BlockSize), int16(m_BlockSize) );

	Iw2DSetColour(0xffffffff);
	Iw2DDrawImage(m_Background, m_GridBGTopLeft, m_GridBGSize);

	for (int i = 0; i < 200; ++i)
	{
		Iw2DSetColour(0xffffffff);
		CIwSVec2 BlockPos( int16(m_GridTopLeft.x + ((i % 10) * (m_BlockSize + 1))), int16(m_GridTopLeft.y + ((int(i / 10)) * (m_BlockSize + 1))) );
		if (m_Blocks[i]->GetType() != Block::NONE)
		{
			Iw2DDrawImage(m_BlockTypeImages[m_Blocks[i]->GetType()], BlockPos, BlockSize);
		}
		
		//// Debug group IDs and staticness
		//if (m_Blocks[i]->IsStatic())
		//{
		//	Iw2DSetColour(0xff2222ff);
		//}
		//else
		//{
		//	Iw2DSetColour(0xffff2222);
		//}
		//char str[3];
		//sprintf(str, "%i", m_Blocks[i]->GetGroupID());
		//Iw2DDrawString(str, BlockPos, BlockSize, IW_2D_FONT_ALIGN_CENTRE, IW_2D_FONT_ALIGN_CENTRE);
	}
}

void Grid::MoveCurrentStructure( T_DIRECTION a_Direction )
{
	bool can_move_left = true;
	bool can_move_right = true;
	//bool can_move_up = true;
	//bool can_move_down = true;

	// Find out whether one of the blocks in the group can't move.
	for(int b = 0; b < 4; ++b)
	{
		int i = m_CurBlocks[b]->GetIndex();
		if((i % 10 == 9) || (m_Blocks[i + 1]->GetType() != Block::NONE &&
							 m_Blocks[i + 1]->GetGroupID() != m_CurrentGroupID))
			can_move_right = false;

		if ((i % 10 == 0) || (m_Blocks[i - 1]->GetType() != Block::NONE &&
							  m_Blocks[i - 1]->GetGroupID() != m_CurrentGroupID))
			can_move_left = false;

		//if (i >= 190 || (m_Blocks[i + 10]->GetType() != Block::NONE &&
		//				 m_Blocks[i + 10]->GetGroupID() != m_CurrentGroupID))
		//	can_move_down = false;

		//if (i < 10 || (m_Blocks[i - 10]->GetType() != Block::NONE &&
		//			   m_Blocks[i - 10]->GetGroupID() != m_CurrentGroupID))
		//	can_move_up = false;
	}
	
	int offset = 0;
	switch (a_Direction)
	{
	case Grid::LEFT:
			if (can_move_left)	offset = -1;
			break;
	case Grid::RIGHT:
			if (can_move_right)	offset = 1;
			break;
	//case Grid::DOWN:
	//		if (can_move_down)	offset = 10;
	//		break;
	//case Grid::UP:
	//		if (can_move_up)	offset = -10;
	//		break;
	}

	// If offset equals 0, the blocks can not move (since the offset is only changed if they can).
	if (offset != 0)
	{
		// Swap blocks.
		if(offset > 0)
			for(int i = 3; i >= 0; --i)
				SwapBlocks(m_CurBlocks[i]->GetIndex(), m_CurBlocks[i]->GetIndex() + offset);
		else
			for(int i = 0; i < 4; ++i)
				SwapBlocks(m_CurBlocks[i]->GetIndex(), m_CurBlocks[i]->GetIndex() + offset);

		m_CurBlockPos.x += offset;

		for(int i = 0; i < 4; ++i)
			// Indicate it is static.
			m_CurBlocks[i]->SetStatic(false);
		// Indicate that a block was moved.
		m_BlockWasMoved = true;
	}
}
void Grid::RotateCurrentStructure( T_DIRECTION a_Direction )
{
	int rotationAdd = 0;
	switch (a_Direction)
	{
	case Grid::LEFT:
		{
			rotationAdd = 1;
			break;
		}
	case Grid::RIGHT:
		{
			rotationAdd = -1;
			break;
		}
	}
	assert(rotationAdd != 0);

	const int startIndex = m_CurBlockPos.x + m_CurBlockPos.y * 10;
	bool canRotate = true;
	for (int x = 0; x < 4; ++x) for (int y = 0; y < 4; ++y)
	{
		// If it's a position that'll be filled when rotated, We can't rotate.
		if (m_BlockPatterns[m_CurBlockPattern][m_CurBlockRotation+rotationAdd][x][y]
			&& x >= 0 && x <= 9 && y < 1906
			&& m_Blocks[startIndex + x + y * 10]->GetType() != Block::NONE
			&& m_Blocks[startIndex + x + y * 10]->GetGroupID() != m_CurrentGroupID)
		{
			canRotate = false;
		}
	}
	if(!canRotate)
		return;

	m_CurBlockRotation = (m_CurBlockRotation + rotationAdd)%4;
	if(m_CurBlockRotation < 0)
		m_CurBlockRotation += 4;
	int i = 0;
	// Move the blocks to their correct position.
	for(int x = 0; x < 4; ++x) for(int y = 0; y < 4; ++y)
	{
		if(m_BlockPatterns[m_CurBlockPattern][m_CurBlockRotation][x][y])
		{
			SwapBlocks(m_CurBlocks[i++]->GetIndex(), startIndex + x + y * 10);
		}
	}

	for(int i = 0; i < 4; ++i)
		// Indicate it is static.
		m_CurBlocks[i]->SetStatic(false);
	// Indicate that a block was moved.
	m_BlockWasMoved = true;
}

int Grid::GetNextBlockIndex()
{
	return m_NextBlockIndex;
}

Block::T_TYPE Grid::GetNextBlockType()
{
	return m_NextBlockType;
}

int Grid::GetNextBlockRotation()
{
	return m_NextBlockRotation;
}

CIw2DImage* Grid::GetBlockTypeImage( Block::T_TYPE a_Type )
{
	return m_BlockTypeImages[a_Type];
}

bool Grid::BlockWasMoved()
{
	return m_BlockWasMoved;
}

void Grid::SpawnBlocks( int a_StructureIndex, int a_StructureRotation, bool a_CheckValid /*= true*/ )
{
	static int static_groupid = 1;
	++static_groupid;

	m_CurBlockPattern = a_StructureIndex;
	m_CurBlockRotation = a_StructureRotation;

	int i = 0;
	for(int x = 0; x < 4; ++x)
		for(int y = 0; y < 4; ++y)
			if(m_BlockPatterns[m_CurBlockPattern][m_CurBlockRotation][x][y])
			{
				m_CurBlocks[i] = m_Blocks[3 + x + y * 10];

				if (a_CheckValid)
				{
					// If the block on which to spawn is taken already...
					if (m_CurBlocks[i]->GetType() != Block::NONE)
					{
						// Switch to game-over.
						Game::GetSingletonPtr()->SwitchGameState(Game::GAMEOVER);
					}
				}

				m_CurBlocks[i]->SetType( m_NextBlockType );
				m_CurBlocks[i]->SetGroupID( static_groupid );
				m_CurBlocks[i]->SetStatic( false );
				m_CurBlocks[i]->SetHasMoved( false );
				i++;
			}

	m_CurBlockPos = CIwSVec2(3, 0);
	m_CurrentGroupID = static_groupid;
}

void Grid::SwapBlocks( int a_Index1, int a_Index2 )
{
	assert(a_Index1 >= 0 && a_Index1 < 200 && a_Index2 >= 0 && a_Index2 < 200);

	Block* tempPtr = m_Blocks[a_Index1];
	m_Blocks[a_Index1] = m_Blocks[a_Index2];
	m_Blocks[a_Index2] = tempPtr;

	m_Blocks[a_Index1]->SetIndex(a_Index1);
	m_Blocks[a_Index2]->SetIndex(a_Index2);
}